package com.dongbao.core.rules.java;

import com.dongbao.core.base.CodeRulesCommonBase;
import com.dongbao.core.rules.CodeRulesBase;
import com.dongbao.entity.AwardedInfo;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.editor.Document;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.*;
import com.intellij.psi.impl.source.PsiClassImpl;
import com.intellij.psi.impl.source.tree.java.*;

import java.util.List;

/**
 *   禁止出现魔法值
 *
 * */
public class MagicPointRules extends CodeRulesCommonBase implements CodeRulesBase {

    private static final Logger LOGGER = Logger.getInstance(MagicPointRules.class);

    public MagicPointRules(VirtualFile afterFile,PsiFile psiFile,Project project) {
        super(afterFile,psiFile,project);
        this.code = "A009";
        this.level = "A";
    }

    /**
     * 执行规则判断
     * */
    @Override
    public void run(List<AwardedInfo> deduction) {
        super.runAllExpressionRow(deduction);
    }

    @Override
    public void validAll(PsiElement elementRow, List<AwardedInfo> deduction, PsiClassImpl psiClass, PsiMethod method){
//        if(method.getName().equals("test2")){
            String text = elementRow.getText();
            PsiElement[] childrens = elementRow.getChildren();
            /* 使用递归计算是否存在魔法值 */
            for(PsiElement children:childrens){
                magicHandle(children,deduction,psiClass,method);
            }
//        }
    }

//    @Override
//    public void validDeclarationUse(PsiElement elementRow, List<AwardedInfo> deduction, PsiClassImpl psiClass, PsiMethod method){
//        if(method.getName().equals("test2")){
//            String text = elementRow.getText();
//            PsiElement[] childrens = elementRow.getChildren();
//            /* 使用递归计算是否存在魔法值 */
//            for(PsiElement children:childrens){
//                magicHandle(children,deduction,psiClass,method);
//            }
//        }
//    }
//
//    /**
//     * 方法调用表达式解析事件
//     * */
//    public void validExpUse(PsiElement elementRow,List<AwardedInfo> deduction,PsiClassImpl psiClass,PsiMethod method){
//        if(method.getName().equals("test2")){
//            String text = elementRow.getText();
//            PsiElement[] childrens = elementRow.getChildren();
//            /* 使用递归计算是否存在魔法值 */
//            for(PsiElement children:childrens){
//                magicHandle(children,deduction,psiClass,method);
//            }
//        }
//    }

    public void magicHandle(PsiElement children,List<AwardedInfo> deduction, PsiClassImpl psiClass, PsiMethod method){
            for(PsiElement childrenItem:children.getChildren()){
                if(childrenItem instanceof PsiLiteralExpressionImpl
                    &&(((PsiLiteralExpressionImpl) childrenItem).getLiteralElementType() == JavaTokenType.INTEGER_LITERAL
                    || ((PsiLiteralExpressionImpl) childrenItem).getLiteralElementType() == JavaTokenType.LONG_LITERAL
                    || ((PsiLiteralExpressionImpl) childrenItem).getLiteralElementType() == JavaTokenType.FLOAT_LITERAL
                    || ((PsiLiteralExpressionImpl) childrenItem).getLiteralElementType() == JavaTokenType.DOUBLE_LITERAL
                    || ((PsiLiteralExpressionImpl) childrenItem).getLiteralElementType() == JavaTokenType.STRING_LITERAL
                    || ((PsiLiteralExpressionImpl) childrenItem).getLiteralElementType() == JavaTokenType.CHARACTER_LITERAL)){
                    Document document = PsiDocumentManager.getInstance(psiClass.getProject()).getDocument(psiClass.getContainingFile());
                    int lineNumber = document.getLineNumber(childrenItem.getTextOffset());

                    /* 判断是否是魔法值 */
                    packDeduction(
                            deduction,
                            psiClass.getName(),
                            psiPackageStatements.get(0).getPackageName(),
                            method.getName(),
                            "禁止出现魔法值",lineNumber,lineNumber);
                }else if(children.getChildren().length>0) {
                    magicHandle(childrenItem,deduction,psiClass,method);
                }
            }
    }

    @Override
    public String describe() {
        return "命名规则";
    }
}
